package com.tust.app.controller;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.tust.app.consts.Constants;
import com.tust.app.domain.TSource;
import com.tust.app.service.TSourceService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.URLEncoder;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Date;
import java.util.List;

@Controller
public class SourceController {
    @Autowired
    private TSourceService sourceService;

    @RequestMapping("/getAllSource2")
    public String getAllSource2(Integer pn, HttpServletRequest request) {
        try {
            String username = (String) request.getSession().getAttribute("username");
            if (username == null){
                return "forward:/checkLogin";
            }
            if (pn == null) {
                pn = 1;
            }
            PageHelper.startPage(pn, Constants.mainPageSize);
            List<TSource> sourceList = sourceService.selectAll();
            PageInfo<TSource> page = new PageInfo<>(sourceList);
            request.setAttribute("sourceList", page);
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("按固定页码做分页查询失败！");
        }

        return "frontPage/allSource";
    }

    @RequestMapping("/getAllSource")
    public String getAllSource(Integer pn, HttpServletRequest request) {
        try {
            if (pn == null) {
                pn = 1;
            }
            PageHelper.startPage(pn, Constants.mainPageSize);
            List<TSource> sourceList = sourceService.selectAll();
            PageInfo<TSource> page = new PageInfo<>(sourceList);
            request.setAttribute("sourceList", page);
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("按固定页码做分页查询失败！");
        }

        return "admin/source/allSource";
    }

    @RequestMapping("/deleteSource")
    public String deleteSource(Integer id, HttpServletRequest request) {
        try {
            // 根据id从数据库中获取要删除的资料信息
            TSource source = sourceService.selectByPrimaryKey(id);

            // 删除数据库中的资料信息
            sourceService.deleteByPrimaryKey(id);

            // 删除对应的文件
            String filePath = request.getServletContext().getRealPath("/upload/source/" + source.getFilename());
            Path fileToDelete = Paths.get(filePath);
            Files.delete(fileToDelete);

            // 重新查询资料列表并设置到request中
            PageHelper.startPage(Constants.mainPageNum, Constants.mainPageSize);
            List<TSource> sourceList = sourceService.selectAll();
            PageInfo<TSource> page = new PageInfo<>(sourceList);
            request.setAttribute("sourceList", page);
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("按固定页码做分页查询失败！");
        }

        return "admin/source/allSource";
    }


    @PostMapping("/uploadSource")
    public String uploadSource(@RequestParam("file") MultipartFile file, HttpServletRequest request) {
        if (file.isEmpty()) {
            return "admin/source/sourceUploadFail"; // 返回错误信息
        }
        try {
            // 获取webapp目录下的upload文件夹路径
            String uploadPath = request.getServletContext().getRealPath("/upload/source");

            // 生成唯一的文件名
            String originalFilename = file.getOriginalFilename();

            // 保存文件到指定目录
            Path targetPath = Paths.get(uploadPath, originalFilename);

            Files.write(targetPath, file.getBytes());

            // 创建 TSource 对象并保存到数据库
            TSource source = TSource.builder().filename(originalFilename).pubtime(new Date().toString()).build();
            // 调用service将source插入数据库
            sourceService.insert(source);

            return "admin/source/sourceUploadSuccess";
        } catch (IOException e) {
            e.printStackTrace();
            return "admin/source/sourceUploadFail"; // 返回错误信息
        }
    }

    @GetMapping("/down")
    public void downloadFile(@RequestParam("filename") String filename, HttpServletRequest request, HttpServletResponse response) {
        if (filename.isEmpty()) {
            return;
        }
        try {
            // 获取webapp目录下的upload文件夹路径
            String uploadPath = request.getServletContext().getRealPath("/upload/source");

            // 保存文件到指定目录
            Path targetPath = Paths.get(uploadPath, filename);

            // 将文件写入输入流
            FileInputStream fileInputStream = new FileInputStream(targetPath.toFile());
            InputStream fis = new BufferedInputStream(fileInputStream);
            byte[] buffer = new byte[fis.available()];
            if (fis.read(buffer) == -1) System.out.println("fis.read wrong in SourceController.java");
            fis.close();

            // 清空response
            response.reset();
            // 设置response的Header
            response.setCharacterEncoding("UTF-8");
            //Content-Disposition的作用：告知浏览器以何种方式显示响应返回的文件，用浏览器打开还是以附件的形式下载到本地保存
            //attachment表示以附件方式下载   inline表示在线打开   "Content-Disposition: inline; filename=文件名.mp3"
            // filename表示文件的默认名称，因为网络传输只支持URL编码的相关支付，因此需要将文件名URL编码后进行传输,前端收到后需要反编码才能获取到真正的名称
            response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(filename, "UTF-8"));
            // 告知浏览器文件的大小
            response.addHeader("Content-Length", "" + filename.length());
            OutputStream outputStream = new BufferedOutputStream(response.getOutputStream());
            response.setContentType("application/octet-stream");
            outputStream.write(buffer);
            outputStream.flush();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
